<?php

/**
 * Kao.php
 * 
 * Kao: PHP Web Framework <http://www.byhuy.com/kao/>.
 * Copyright 2007-2008, Huy Nguyen <http://www.byhuy.com/>.
 * 
 * Licensed under The MIT License
 * Redistributions of files must retain the above copyright notice.
 * 
 */

/**
 * Class Kao: The static foundation class for Kao
 *
 * Can not get instance of this class
 * 
 * @author Huy Nguyen <http://www.byhuy.com/>
 * @since 0.1
 */

class Kao
{
     
    /**
     * The list of component types that Kao supports
     */
    const COMP_VENDOR    = 'vendor';
    const COMP_FORM      = 'form';
    const COMP_HELPER    = 'helper';
    const COMP_RECORD    = 'record';
    const COMP_VALIDATOR = 'validator';
    const COMP_DAO       = 'dao';
    
    /**
     * The framework dir absolute path
     */
    protected static $_frameworkPath = null;
    
    
    /**
     * Component directory name
     * 
     * Define the list of component paths
     * 'component_type_name' => 'dir_name';
     */
    public static $componentDirs = array (
        self::COMP_VENDOR    => 'vendors', 
        self::COMP_FORM      => 'forms',
        self::COMP_HELPER    => 'helpers',
        self::COMP_RECORD    => 'records',
        self::COMP_VALIDATOR => 'validators',
        self::COMP_DAO       => 'daos'
    );
    
    /**
     * The private constuctor
     * 
     * Make sure no one can get an instance of the class
     */
    private function __construct()
    {
            
    }
    
    
    /**
     * Converts camelCase style name to underscore style
     * 
     * @param string
     * @return string
     */
    public static function toUnderscore($camelCase)
    {
        if (!is_string($camelCase))
        {
            return $camelCase;
        }
        
        $underscore = '';
        $len = strlen($camelCase);
        
        for ($i = 0; $i < $len; $i++)
        {
            if (preg_match('/[A-Z]/', $camelCase[$i]) && ($i > 0))
            {
                $underscore .= '_' . $camelCase[$i];
            }
            else
            {
                $underscore .= $camelCase[$i];
            }
        }
        return strtolower($underscore);
    }
    
    /**
     * Converts underscore style name to camelCase style
     * 
     * @param string
     * @return string
     */
    public static function toCamelCase($underscore)
    {
        if (!is_string($underscore))
        {
            return $underscore;
        }
        
        $parts = explode('_', $underscore);
        
        $camelCase = '';
        $len = count($parts);
        
        for ($i = 0; $i < $len; $i++)
        {
            $camelCase .= ($i == 0) ? $parts[$i] : ucfirst($parts[$i]);
        }
        return $camelCase;
    }
    
    
    /**
     * Checks existent and return the full path of a file. 
     * 
     * First, checks in the application path. If the file does not exist, 
     * check in the common application path. 
     * If the file does not exist in neither two path, return false.
     * 
     * @param string $filePath
     * @param boolean $checkInCommon
     * @return mixed
     * 
     */
    public static function getFullPath($filePath, $checkInCommon = true)
    {
        $app = Kao_App::getInstance();
        $paths = array();
        
        if ($app->getAppPath())
        {
            $paths[] = $app->getAppPath();
        }
        
        if ($checkInCommon && (null !== self::$_frameworkPath))
        {
            $paths[] = self::$_frameworkPath . DIRECTORY_SEPARATOR . 'common';
        }
        
        foreach ($paths as $path)
        {
            $finalPath = $path . DIRECTORY_SEPARATOR . $filePath;
            if (file_exists($finalPath) && is_readable($finalPath))
            {
                return $finalPath;
            }
        }
        return false;
    }
    
    public static function requireFile($filePath, $checkInCommon = true)
    {
        $path = self::getFullPath($filePath, $checkInCommon);
        
        if (false !== $path)
        {
            // TODO re-check this error message
            trigger_error('require_once(\'' . $filePath . '\'): failed to open stream: No such file or directory', E_USER_ERROR);
        }
        
        return require_once $path;
    }
    
    /**
     * Init the framework path
     */
    public static function initFramework($frameworkPath)
    {
         self::$_frameworkPath = $frameworkPath;
    }
}

